use std::fs::File;
use std::io::BufReader;
use std::path::Path;
use rustls::{Certificate, PrivateKey, ServerConfig, ClientConfig};
use rustls_pemfile::{certs, pkcs8_private_keys};
use crate::common::Result;
use serde::{Deserialize, Serialize};
use std::path::PathBuf;

#[derive(Debug, Clone, Serialize, Deserialize)]
pub struct TlsConfig {
    pub cert_file: PathBuf,
    pub key_file: PathBuf,
    pub ca_file: Option<PathBuf>,
    pub verify_client: bool,
}

impl Default for TlsConfig {
    fn default() -> Self {
        Self {
            cert_file: PathBuf::from("certs/server.crt"),
            key_file: PathBuf::from("certs/server.key"),
            ca_file: Some(PathBuf::from("certs/ca.crt")),
            verify_client: false,
        }
    }
}

impl TlsConfig {
    pub fn new(cert_file: PathBuf, key_file: PathBuf, ca_file: Option<PathBuf>) -> Self {
        Self {
            cert_file,
            key_file,
            ca_file,
            verify_client: false,
        }
    }
    
    pub fn with_client_verification(mut self, verify: bool) -> Self {
        self.verify_client = verify;
        self
    }
}

/// TLS服务器配置
pub struct TlsServerConfig {
    pub config: ServerConfig,
}

/// TLS客户端配置
pub struct TlsClientConfig {
    pub config: ClientConfig,
}

impl TlsServerConfig {
    pub fn new(cert_path: &Path, key_path: &Path) -> Result<Self> {
        let cert_file = File::open(cert_path)
            .map_err(|e| crate::common::ManagerError::CertificateError(format!("无法打开证书文件: {}", e)))?;
        let key_file = File::open(key_path)
            .map_err(|e| crate::common::ManagerError::CertificateError(format!("无法打开私钥文件: {}", e)))?;

        let mut cert_reader = BufReader::new(cert_file);
        let mut key_reader = BufReader::new(key_file);

        let cert_chain = certs(&mut cert_reader)
            .map_err(|e| crate::common::ManagerError::CertificateError(format!("解析证书失败: {}", e)))?
            .into_iter()
            .map(Certificate)
            .collect();

        let mut keys: Vec<PrivateKey> = pkcs8_private_keys(&mut key_reader)
            .map_err(|e| crate::common::ManagerError::CertificateError(format!("解析私钥失败: {}", e)))?
            .into_iter()
            .map(PrivateKey)
            .collect();

        if keys.is_empty() {
            return Err(crate::common::ManagerError::CertificateError("未找到私钥".to_string()));
        }

        let config = ServerConfig::builder()
            .with_safe_defaults()
            .with_no_client_auth()
            .with_single_cert(cert_chain, keys.remove(0))
            .map_err(|e| crate::common::ManagerError::CertificateError(format!("创建TLS配置失败: {}", e)))?;

        Ok(Self { config })
    }
}

impl TlsClientConfig {
    pub fn new(ca_cert_path: &Path, client_cert_path: Option<&Path>, client_key_path: Option<&Path>) -> Result<Self> {
        let mut root_store = rustls::RootCertStore::empty();
        
        // 加载CA证书
        let ca_cert_file = File::open(ca_cert_path)
            .map_err(|e| crate::common::ManagerError::CertificateError(format!("无法打开CA证书文件: {}", e)))?;
        let mut ca_reader = BufReader::new(ca_cert_file);
        
        let ca_certs = certs(&mut ca_reader)
            .map_err(|e| crate::common::ManagerError::CertificateError(format!("解析CA证书失败: {}", e)))?;
        
        for cert in ca_certs {
            root_store.add(&rustls::Certificate(cert))
                .map_err(|e| crate::common::ManagerError::CertificateError(format!("添加CA证书失败: {}", e)))?;
        }

        let mut config_builder = ClientConfig::builder()
            .with_safe_defaults()
            .with_root_certificates(root_store);

        // 如果提供了客户端证书和私钥，则配置客户端认证
        if let (Some(cert_path), Some(key_path)) = (client_cert_path, client_key_path) {
            let cert_file = File::open(cert_path)
                .map_err(|e| crate::common::ManagerError::CertificateError(format!("无法打开客户端证书文件: {}", e)))?;
            let key_file = File::open(key_path)
                .map_err(|e| crate::common::ManagerError::CertificateError(format!("无法打开客户端私钥文件: {}", e)))?;

            let mut cert_reader = BufReader::new(cert_file);
            let mut key_reader = BufReader::new(key_file);

            let cert_chain = certs(&mut cert_reader)
                .map_err(|e| crate::common::ManagerError::CertificateError(format!("解析客户端证书失败: {}", e)))?
                .into_iter()
                .map(Certificate)
                .collect();

            let mut keys: Vec<PrivateKey> = pkcs8_private_keys(&mut key_reader)
                .map_err(|e| crate::common::ManagerError::CertificateError(format!("解析客户端私钥失败: {}", e)))?
                .into_iter()
                .map(PrivateKey)
                .collect();

            if keys.is_empty() {
                return Err(crate::common::ManagerError::CertificateError("未找到客户端私钥".to_string()));
            }

            config_builder = config_builder.with_client_auth_cert(cert_chain, keys.remove(0))
                .map_err(|e| crate::common::ManagerError::CertificateError(format!("配置客户端认证失败: {}", e)))?;
        }

        let config = config_builder.with_no_client_auth();

        Ok(Self { config })
    }
} 